package org.smart4j.framework.helper;

import com.sun.org.apache.bcel.internal.generic.IF_ACMPEQ;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.io.FileUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.smart4j.framework.bean.FileParam;
import org.smart4j.framework.bean.FormParam;
import org.smart4j.framework.bean.ParamNew;
import org.smart4j.framework.util.StreamUtil;

import javax.servlet.ServletContext;
import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * 文件上传助手
 */
public final class UploadHelper {
    private static  final Logger LOGGER = LoggerFactory.getLogger(UploadHelper.class);

    /**
     * commons-apache 提供的上传类
     */
    private static ServletFileUpload servletFileUpload;

    public static void init(ServletContext servletContext){
        File responsitory  =(File) servletContext.getAttribute("javax.servlet.container.tempdir");
        //初始化serverFileUpload对象
        servletFileUpload = new ServletFileUpload(new DiskFileItemFactory(DiskFileItemFactory.DEFAULT_SIZE_THRESHOLD,responsitory));

        int uploadLimit = ConfigHelper.getAppUploadLimit();
        if (uploadLimit != 0){
            servletFileUpload.setFileSizeMax(uploadLimit * 1024 *1024);
        }
    }

    /**
     * 判断请求是否multipart类型
     * @param request
     * @return
     */
    public static boolean isMultipart(HttpServletRequest request){
        return servletFileUpload.isMultipartContent(request);
    }


    /**
     * 创建请求对象 ParamNew
     * @param request
     * @return
     * @throws IOException
     */
    public static ParamNew createParam(HttpServletRequest request) throws IOException{
        ArrayList<FormParam> formParams = new ArrayList<>();
        ArrayList<FileParam> fileParams = new ArrayList<>();
        try {
            Map<String, List<FileItem>> fileItemListMap = servletFileUpload.parseParameterMap(request);
           for (Map.Entry<String,List<FileItem>> entry : fileItemListMap.entrySet()){
               String fieldName = entry.getKey();
               List<FileItem> fileItemList = entry.getValue();
               if (CollectionUtils.isNotEmpty(fileItemList)){
                   for (FileItem fileItem : fileItemList){

                       if (fileItem.isFormField()){
                           String fieldValue = fileItem.getString("UTF-8");
                           formParams.add(new FormParam(fieldName,fieldValue));
                       }else{
                           String fileName =StreamUtil.getRealFileName( new String(fileItem.getName().getBytes(),"UTF-8"));
                           if (fileName != null){
                               Long fileSize = fileItem.getSize();
                               String contentType = fileItem.getContentType();
                               InputStream inputStream = fileItem.getInputStream();
                               fileParams.add(new FileParam(fieldName,fileName,fileSize,contentType,inputStream));
                           }
                       }
                   }
               }
           }

        } catch (FileUploadException e) {
            LOGGER.error("create Param failure",e);
            throw new RuntimeException(e);
        }

        return new ParamNew(formParams,fileParams);
    }


    /**
     * 上传文件
     * @param basePath
     * @param fileParam
     */
    public static void uploadFile(String basePath,FileParam fileParam){

        if (fileParam != null){
            String filePath = basePath +fileParam.getFileName();
            StreamUtil.createFile(filePath);
            try {
                InputStream inputStream = new BufferedInputStream(fileParam.getInputStream());
                OutputStream outputStream = new BufferedOutputStream(new FileOutputStream(filePath));
                StreamUtil.copyStream(inputStream,outputStream);
            } catch (FileNotFoundException e) {
                LOGGER.error("upload file failure",e);
                throw  new RuntimeException(e);
            }


        }
    }

    /**
     * 批量上传文件
     * @param basePath
     * @param fileParamList
     */
    public static void uploadFile(String basePath,List<FileParam> fileParamList){

        if (CollectionUtils.isNotEmpty(fileParamList)){
            try {
                for (FileParam fileParam : fileParamList){
                    uploadFile(basePath,fileParam);
                }
            } catch (Exception e) {
                LOGGER.error("bath upload file failure",e);
                throw new RuntimeException(e);
            }
        }
    }




















}
